#include "napi/native_api.h"
#include <js_native_api.h>
#include <hilog/log.h>
#include "native_callback.h"
#include <thread>
#include <chrono>

// 异步工作数据结构
struct AsyncWorkData {
    napi_env env = nullptr;
    ResultCallback callback;
    std::string input;
    std::string result;
    bool success = false;
};

// 异步执行函数（在工作线程中执行）
static void ExecuteWork(napi_env env, void* data) {
    AsyncWorkData* workData = static_cast<AsyncWorkData*>(data);
    
    // 模拟耗时操作
    std::this_thread::sleep_for(std::chrono::milliseconds(5000));
    
    // 业务处理逻辑
    workData->result = "处理结果: " + workData->input + " - 完成时间: " + std::to_string(time(nullptr));
    workData->success = true;
    
    OH_LOG_Print(LOG_APP, LOG_INFO, LOG_DOMAIN, LOG_TAG, "ExecuteWork: 业务处理完成");
}

// 完成回调函数（在主线程中执行）
static void CompleteWork(napi_env env, napi_status status, void* data) {
    AsyncWorkData* workData = static_cast<AsyncWorkData*>(data);
    
    if (status != napi_ok) {
        OH_LOG_ERROR(LOG_APP, "CompleteWork: 异步工作状态错误");
        return;
    }
    
    // 调用回调函数
    workData->callback(env, workData->result.c_str());
    
    OH_LOG_Print(LOG_APP, LOG_INFO, LOG_DOMAIN, LOG_TAG, "CompleteWork: 回调执行完成");
}


// 模拟异步业务处理
void processBusinessAsync(napi_env env, const char* input, ResultCallback callback) {
    OH_LOG_Print(LOG_APP, LOG_INFO, LOG_DOMAIN, LOG_TAG, "开始调用processBusinessAsync函数");
    
    // 注意：注释掉的异步代码调用arkts回调函数应用会崩溃，
    // 在ArkTS的NAPI环境中，在多线程（如std::thread）中直接调用回调函数可能会导致崩溃，因为NAPI环境不是线程安全的。我们需要使用Node-API的线程安全函数来在异步线程中调用回调。
    /*std::thread([env, input = std::string(input), callback]() {
        // 模拟耗时操作
        OH_LOG_Print(LOG_APP, LOG_INFO, LOG_DOMAIN, LOG_TAG, "开始调用processBusinessAsync函数模拟耗时操作");
        std::this_thread::sleep_for(std::chrono::seconds(1));
        
        // 业务处理逻辑
        std::string result = "处理结果: " + std::string(input) + " - 完成时间: " + std::to_string(time(nullptr));
        OH_LOG_Print(LOG_APP, LOG_INFO, LOG_DOMAIN, LOG_TAG, "开始调用processBusinessAsync函数结束， %{public}s", result.c_str());
        
        // 调用回调函数返回结果
        callback(env, result.c_str());
    }).detach();*/
    
    // 同步调用arkts回调函数正常
//    std::string result = "处理结果: " + std::string(input) + " - 完成时间: " + std::to_string(time(nullptr));
//    callback(env, result.c_str());
    
    // 以下是异步调用arkts回调函数的替代方案，使用 NAPI 异步工作（推荐）
    // 解决方案：
    //  1. 使用napi_create_async_work来创建异步工作。
    //  2. 在异步工作的完成回调中调用ArkTS的回调函数，因为完成回调是在主线程中执行的。
    // 步骤如下：
    //      a. 定义一个结构体，用于传递异步工作的数据。
    //      b. 创建异步工作，并指定执行函数和完成函数。
    //      c. 在执行函数（在后台线程运行）中处理业务逻辑，将结果保存在结构体中。
    //      d. 在完成函数（在主线程运行）中调用回调函数，并传递结果。
    
    //  创建异步工作数据
    AsyncWorkData* workData = new AsyncWorkData();
    workData->env = env;
    workData->callback = callback;
    workData->input = input;
    
    // 创建异步工作
    napi_value resourceName;
    napi_create_string_utf8(env, "AsyncBusinessWork", NAPI_AUTO_LENGTH, &resourceName);
    
    napi_async_work asyncWork;
    napi_create_async_work(
        env,
        nullptr,
        resourceName,
        ExecuteWork,
        CompleteWork,
        workData,
        &asyncWork
    );
    
    // 队列化异步工作
    napi_queue_async_work(env, asyncWork);
    
    OH_LOG_Print(LOG_APP, LOG_INFO, LOG_DOMAIN, LOG_TAG, "funcC: 异步工作已启动");
}

